package org.xbs.demo1.interceptor;

import jakarta.servlet.http.HttpServletRequest;
import jakarta.servlet.http.HttpServletResponse;
import lombok.extern.slf4j.Slf4j;
import org.springframework.stereotype.Component;
import org.springframework.web.servlet.HandlerInterceptor;
import org.xbs.demo1.pojo.JwtUtils;

@Slf4j
@Component//拦截器是springboot中的组件，这是告诉springboot这是一个拦截器
public class Interceptor implements HandlerInterceptor {
    //客户端访问到指定资源前进行的方法，也是拦截到请求后执行的方法
    @Override
    public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception {
        log.info("拦截器拦截到请求");
        //1.获取请求的路径
        String requestURI = request.getRequestURI();
        //2.判断是否为登录请求
        if (requestURI.equals("/login")){
            log.info("用户正在尝试进行登录操作");
            return true;
        }
        //3.获得请求头中的token，token一般放在请求头中
        String token = request.getHeader("token");//这代表要获得请求头中的token字段
        if(token == null || token.isEmpty()){
            log.info("令牌为空，响应401");
            response.setStatus(401);//设置状态码为401，代表用户没有登录
            return false;
        }
        //4.若token存在，但是令牌校验失败，也返回错误信息
        try{
            JwtUtils.parseJWTClaims(token);//此处用密钥校验jwt令牌，若无法解析会抛出异常
        }catch (Exception e){
            log.info("令牌校验失败，响应401");
            response.setStatus(401);//设置状态码为401，代表用户没有登录
            return false;
        }
        //5.token存在并且校验成功，则放行，并返回用户信息
        log.info("用户令牌校验成功，响应200");
        response.setStatus(200);
        return true;

    }
    //客户端访问指定资源后进行的方法，也是拦截到请求后执行的方法
    @Override
    public void postHandle(HttpServletRequest request, HttpServletResponse response, Object handler, org.springframework.web.servlet.ModelAndView modelAndView) throws Exception {
        log.info("拦截器放行请求");
        HandlerInterceptor.super.postHandle(request, response, handler, modelAndView);
    }
    //第三种方法是渲染图的方法，是在响应前服务器端进行的最后一个方法，虽然现在一般不用渲染图，但是这个方法因为最后会被执行所以可以用来干一些收尾工作
    //比如记录一个用户的访问记录，(这个接口预留给我，用于扩展功能，或者说给超级管理员开这个权限)
    @Override
    public void afterCompletion(HttpServletRequest request, HttpServletResponse response, Object handler, Exception ex) throws Exception {
        log.info("拦截器最后操作");
        HandlerInterceptor.super.afterCompletion(request, response, handler, ex);
    }
}
